<?php
###
#  Baing PHP 框架 1.0.0
#  http://baing.co/
#
#  Copyright: 白晓阳
#  License: CC BY-NC-SA 4.0
#  https://creativecommons.org/licenses/by-nc-sa/4.0/deed.zh
###

namespace bai\feature;

use bai\Response;


abstract class BaingException extends \Exception
{
    protected const CODE_DEFAULT = Response::STATUS_ERROR;

    protected $params = null;

    public static function format(\Throwable $e): string
    {
        $output = $e::class;
        if ($message = $e->getMessage()) {
            $output .= " - $message";
        }
        $file = $e->getFile();
        $line = $e->getLine();
        $output .= " at $file($line)";
        return $output;
    }

    public static function formatExport(\Throwable $e): array
    {
        $output = [
            'message' => 'SystemException',
            'params' => $e::class,
        ];
        if ($message = $e->getMessage()) {
            $output['params'] .= " - $message";
        }
        return $output;
    }

    public function __construct(string $message = '', $params = null, int $code = 0, \Throwable $previous = null)
    {
        parent::__construct($message, $code ?: static::CODE_DEFAULT, $previous);
        $this->params = $params;
    }

    public function getFullMessage(): string
    {
        $output = substr(static::class, strlen(__NAMESPACE__) + 1);
        if ($this->message) {
            $output .= "[$this->message]";
        }
        if ($this->params) {
            $output .= ' - ' . json_encode($this->params, true);
        }
        $output .= " at $this->file($this->line)";
        return $output;
    }

    public function export(): array
    {
        $message = substr(static::class, strlen(__NAMESPACE__) + 1);
        if ($this->message) {
            $message = "$message.$this->message";
        }
        $output = [
            'message' => $message
        ];
        if ($this->params) {
            $output['params'] = $this->params;
        }
        return $output;
    }
}

class RequestException extends BaingException
{
    protected const CODE_DEFAULT = Response::STATUS_BAD_REQUEST;
}


class RuntimeException extends BaingException
{
}


class ResourceException extends BaingException
{
}


class ProcessException extends BaingException
{
}


class ExtensionException extends BaingException
{
}


class SystemException extends BaingException
{
}
